#include "stdafx.h"
#include "Framework\lego_3D.h"
#include "Framework\lego_3Ddoc.h"
#include "Framework\lego_3Dview.h"
#include "DLG_2DSplineSetting.h"
#include "2dspline/selectedpolygon.h"

#pragma warning(disable : 4800)
IMPLEMENT_DYNAMIC(CDLG_2DSpline_Setting, CDialog)

CDLG_2DSpline_Setting::CDLG_2DSpline_Setting(CWnd* pParent /*=NULL*/)
	: CDialog(CDLG_2DSpline_Setting::IDD, pParent)
{
	m_pView = NULL;
	m_pDoc = NULL;
}

CDLG_2DSpline_Setting::CDLG_2DSpline_Setting(CLego_3Dview *pView)
{
	m_pView = pView;
}

CDLG_2DSpline_Setting::~CDLG_2DSpline_Setting()
{
}

CLego_3Dview* CDLG_2DSpline_Setting::GetMainView(void)
{
	CLego_3Dapp *pApp = (CLego_3Dapp*)AfxGetApp();
	CMainFrame *pMainFrame = (CMainFrame*)pApp->m_pMainWnd;
	CChildFrame *pFrame = (CChildFrame*)pMainFrame->GetActiveFrame();
	return (CLego_3Dview*)pFrame->m_wndSplitter.GetPane(0, 0);
}


BOOL CDLG_2DSpline_Setting::Create( void )
{
	return CDialog::Create(CDLG_2DSpline_Setting::IDD);
}

void CDLG_2DSpline_Setting::OnOK()
{
	if (m_pView != NULL) {	// non-modal
		UpdateData(TRUE);
		m_pView->PostMessage(1, IDOK);
	} else {
		CDialog::OnOK();
	}
}

void CDLG_2DSpline_Setting::OnBnClickedOk()
{
	OnOK();
}

void CDLG_2DSpline_Setting::OnCancel()
{
	CWnd::ShowWindow(SW_HIDE);
}

void CDLG_2DSpline_Setting::Re_display()
{
	CWnd::ShowWindow(SW_SHOW);
}

BOOL CDLG_2DSpline_Setting::OnInitDialog() 
{
	CDialog::OnInitDialog();
	if (m_pView == NULL)	m_pView = GetMainView();
	m_pDoc = (CLego_3Ddoc*)m_pView->GetDocument();
	
	//input
	CheckControlInputSpline.SetCheck(m_pDoc->m_ImageMouseCtrl==INPUTSPLINE);
	CheckControlInputPoly.SetCheck(m_pDoc->m_ImageMouseCtrl==INPUTPOLY);
	//display
	m_bShowSpline = true;
	m_bShowSplineCurve = true;
	m_bShowSplineVertex = true;
	m_bShowSplineVertexIndex = false;
	m_bShowSplineColorLine = false;
	m_bShowNormal =false;
	CheckControlShowSpline.EnableWindow(true);
	CheckControlShowSplineVertex.EnableWindow(m_bShowSpline);
	CheckControlShowSplineCurve.EnableWindow(m_bShowSpline);
	CheckControlShowNormal.EnableWindow(m_bShowSpline);
	CheckControlShowSplineVertexIndex.EnableWindow(m_bShowSpline);
	CheckControlShowSplineColorLine.EnableWindow(m_bShowSpline);
	CheckControlShowSpline.SetCheck(m_bShowSpline);  //show spline by default.
	CheckControlShowSplineCurve.SetCheck(m_bShowSplineCurve);
	CheckControlShowSplineVertex.SetCheck(m_bShowSplineVertex);  
	CheckControlShowNormal.SetCheck(m_bShowNormal);
	CheckControlShowSplineVertexIndex.SetCheck(m_bShowSplineVertexIndex);  
	CheckControlShowSplineColorLine.SetCheck(m_bShowSplineColorLine); 
	//not show spline in Mesh View by default.
	m_bShowInMeshView = false;
	CheckControlShowInMeshView.EnableWindow(m_pDoc->pSideDoc!=NULL);
	CheckControlShowInMeshView.SetCheck(m_bShowInMeshView);  
	//sample
	m_bOnlyIncrease = true;
	CheckControlKeepOriginV.EnableWindow(true);
	CheckControlKeepOriginV.SetCheck(m_bOnlyIncrease);
	m_SliderSample.SetRange(1, 100, TRUE);
	m_SliderSample.SetPos(50);
	m_SliderSample.EnableWindow(TRUE);
	EDTTriAvgArea.SetWindowText("100.0");
	m_holeSet.clear();
	//SetDlgItemText(IDC_EDIT_VERTEXNUMBER, str);
	SetWindowPos(NULL, 500, 74, 182, 440, SWP_SHOWWINDOW);
	return TRUE;  // return TRUE unless you set the focus to a control
}

void CDLG_2DSpline_Setting::DoDataExchange(CDataExchange* pDX)
{
	CDialog::DoDataExchange(pDX);
	//input
	DDX_Control(pDX,IDC_RADIO_2DSPLINE_DRAWTYPE_SPLINE,	CheckControlInputSpline);
	DDX_Control(pDX,IDC_RADIO_2DSPLINE_DRAWTYPE_POLY,	CheckControlInputPoly);
	//sample
	DDX_Control(pDX,	ID_SLIDER_2DSPLINE_SAMPLE,			 m_SliderSample);
	DDX_Control(pDX,	IDC_CHECK_2DSPLINE_KEEPORIGINVERTEX, CheckControlKeepOriginV);
	//display
	DDX_Control(pDX, IDC_CHECK_SHOW_SPLINE,					CheckControlShowSpline);
	DDX_Control(pDX, IDC_CHECK_SHOW_SPLINE_CURVE,			CheckControlShowSplineCurve);
	DDX_Control(pDX, IDC_CHECK_SHOW_SPLINE_NORMAL,			CheckControlShowNormal);
	DDX_Control(pDX, IDC_CHECK_SHOW_SPLINE_VERTEX,			CheckControlShowSplineVertex);
	DDX_Control(pDX, IDC_CHECK_SHOW_SPLINE_VERTEX_INDEX,	CheckControlShowSplineVertexIndex);
	DDX_Control(pDX, IDC_CHECK_SHOW_COLORLINE,				CheckControlShowSplineColorLine);
	DDX_Control(pDX, IDC_CHECK_SHOW_SPLINE_IN_MESH_VIEW,	CheckControlShowInMeshView);
	DDX_Control(pDX, IDC_EDIT_AVG_TRI_AREA,					EDTTriAvgArea);	
	DDX_Control(pDX, IDC_CHECK_ADD_FRAME_AS_BORDER_FOR_TRIG,CHKAddFrameAsBorder);	
	
}

/*Short Cut: Ctrl+A: select all ; Delete: delete*/
BOOL   CDLG_2DSpline_Setting::PreTranslateMessage(MSG*   pMsg)    
{  
	if(	pMsg->message==WM_KEYDOWN && pMsg->wParam=='A' && GetAsyncKeyState(VK_LCONTROL)<0 )
		OnBnClickedButton2dsplineSelectall();
	else	if(	GetAsyncKeyState(VK_DELETE)<0 )	
		OnBnClickedButton2dsplineDelete();
	return   CDialog::PreTranslateMessage(pMsg);  
}   

BEGIN_MESSAGE_MAP(CDLG_2DSpline_Setting, CDialog)
	ON_WM_HSCROLL()
	ON_BN_CLICKED(IDC_RADIO_2DSPLINE_DRAWTYPE_SPLINE,	OnButtonClickRatioInputSpline)
	ON_BN_CLICKED(IDC_RADIO_2DSPLINE_DRAWTYPE_POLY,		OnBnClickedRadioInputPoly)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_SELECT,			OnBnClickedButtonSplineSelect)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_MODIFY,			OnBnClickedButtonSplineModify)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_REVERSE_ORDER,	OnBnClickedButton2dsplineReverseOrder)
	ON_BN_CLICKED(IDC_CHECK_SHOW_SPLINE,				OnBnClickedCheckShowSpline)
	ON_BN_CLICKED(IDC_CHECK_SHOW_SPLINE_CURVE,			OnBnClickedCheckShowSplineCurve)
	ON_BN_CLICKED(IDC_CHECK_SHOW_SPLINE_VERTEX,			OnBnClickedCheckShowSplineVertex)
	ON_BN_CLICKED(IDC_CHECK_SHOW_SPLINE_VERTEX_INDEX,	OnBnClickedCheckShowSplineVertexIndex)
	ON_BN_CLICKED(IDC_CHECK_SHOW_COLORLINE,				OnBnClickedCheckShowColorline)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_SAVE,				OnBnClickedButton2dsplineSave)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_LOAD,				OnBnClickedButton2dsplineLoad)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_DELETE,			OnBnClickedButton2dsplineDelete)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_ADD_FROMFILE, 	OnBnClickedButton2dsplineAddFromfile)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_SELECTALL,		OnBnClickedButton2dsplineSelectall)
	ON_BN_CLICKED(IDC_CHECK_SHOW_SPLINE_IN_MESH_VIEW,	OnBnClickedCheckShowSplineInMeshView)
	ON_BN_CLICKED(IDC_CHECK_SHOW_SPLINE_NORMAL,			OnBnClickedCheckShowSplineNormal)
	ON_BN_CLICKED(IDC_CHECK_2DSPLINE_KEEPORIGINVERTEX,	OnBnClickedCheck2dsplineKeepOriginVertex)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_CLOSE_UNCLOSE,	OnBnClickedButton2dsplineCloseUnclose)
	//ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_TRIANGULATION,	OnBnClickedButton2dsplineTriangulation)
	ON_BN_CLICKED(IDC_BUTTON_2DSPLINE_SET_HOLES_FOR_TRIG, &CDLG_2DSpline_Setting::OnBnClickedButton2dsplineSetHolesForTrig)
END_MESSAGE_MAP()

void CDLG_2DSpline_Setting::OnButtonClickRatioInputSpline()
{
	if( m_pDoc->m_ImageMouseCtrl == INPUTSPLINE )
		return ;
	m_pDoc->AddNewPolygon( false );
	m_pDoc->ClearSelectedPolys();
	m_pDoc->m_ImageMouseCtrl = INPUTSPLINE;
	CheckControlInputSpline.SetCheck(m_pDoc->m_ImageMouseCtrl==INPUTSPLINE);
	CheckControlInputPoly.SetCheck(m_pDoc->m_ImageMouseCtrl==INPUTPOLY);
}

void CDLG_2DSpline_Setting::OnBnClickedRadioInputPoly()
{
	if(m_pDoc->m_ImageMouseCtrl == INPUTPOLY)
		return ;
	m_pDoc->AddNewPolygon( false );
	m_pDoc->ClearSelectedPolys();
	m_pDoc->m_ImageMouseCtrl  = INPUTPOLY;
	CheckControlInputSpline.SetCheck(m_pDoc->m_ImageMouseCtrl==INPUTSPLINE);
	CheckControlInputPoly.SetCheck(m_pDoc->m_ImageMouseCtrl==INPUTPOLY);
}

void CDLG_2DSpline_Setting::OnBnClickedButtonSplineSelect()
{
	if( m_pDoc->m_ImageMouseCtrl == SELECT )
		return ;
	m_pDoc->AddNewPolygon( false );
	m_pDoc->ClearSelectedPolys();
	m_pDoc->m_ImageMouseCtrl = SELECT;
	m_pView->InvalidateRect(NULL,false);
	CheckControlInputSpline.SetCheck(false);
	CheckControlInputPoly.SetCheck(false);
}

void CDLG_2DSpline_Setting::OnBnClickedButton2dsplineSelectall()
{
	m_pDoc->SelectAllSpline();
}

void CDLG_2DSpline_Setting::OnBnClickedButtonSplineModify()
{
	if( m_pDoc->m_ImageMouseCtrl == MODIFY )
		return ;
	m_pDoc->AddNewPolygon( false );
	m_pDoc->ClearSelectedPolys();
	m_pDoc->m_ImageMouseCtrl= MODIFY;
	m_pView->m_bShowSplineVertex = TRUE;
	m_pView->InvalidateRect(NULL,false);
	CheckControlInputSpline.SetCheck(false);
	CheckControlInputPoly.SetCheck(false);
}

void CDLG_2DSpline_Setting::OnBnClickedButton2dsplineReverseOrder()
{
	m_pDoc->ReverseVertexOrder();
	m_pView->InvalidateRect(NULL,false);
	if(m_pDoc->pSideDoc==NULL)	return;
	if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
	m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
}

void CDLG_2DSpline_Setting::OnBnClickedButton2dsplineDelete()
{
	m_pDoc->DeleteSelectedPolygons();
	if(m_pDoc->pSideDoc==NULL)	return;
	if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
	m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
}

void CDLG_2DSpline_Setting::OnBnClickedCheckShowSpline()
{
	m_bShowSpline = !m_bShowSpline;
	m_pView->m_bShowSpline =m_bShowSpline;
	CheckControlShowSpline.SetCheck(m_bShowSpline); 
	CheckControlShowSplineVertex.EnableWindow(m_bShowSpline);
	CheckControlShowSplineVertexIndex.EnableWindow(m_bShowSpline);
	CheckControlShowSplineColorLine.EnableWindow(m_bShowSpline);
	m_pView->InvalidateRect(NULL,false);
}

void CDLG_2DSpline_Setting::OnBnClickedCheckShowSplineCurve()
{
	m_bShowSplineCurve = !m_bShowSplineCurve;
	m_pView->m_bShowSplineCurve =m_bShowSplineCurve;
	CheckControlShowSplineCurve.SetCheck(m_bShowSplineCurve);
	m_pView->InvalidateRect(NULL,false);
	if(m_pDoc->pSideDoc==NULL)	return;
	if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
	m_pDoc->pSideDoc->m_pView->m_bShowSplineCurve 
		= m_pView->m_bShowSplineCurve;
	m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
}

void CDLG_2DSpline_Setting::OnBnClickedCheckShowSplineVertex()
{
	m_bShowSplineVertex = !m_bShowSplineVertex;
	m_pView->m_bShowSplineVertex =m_bShowSplineVertex;
	CheckControlShowSplineVertex.SetCheck(m_bShowSplineVertex);
	CheckControlShowSplineVertexIndex.EnableWindow(m_bShowSplineVertex);
	m_pView->InvalidateRect(NULL,false);
	if(m_pDoc->pSideDoc==NULL)	return;
	if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
	m_pDoc->pSideDoc->m_pView->m_bShowSplineVertex 
		= m_pView->m_bShowSplineVertex;
	m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
}

void CDLG_2DSpline_Setting::OnBnClickedCheckShowSplineVertexIndex()
{
	m_bShowSplineVertexIndex = !m_bShowSplineVertexIndex;
	m_pView->m_bShowSplineVertexIndex = m_bShowSplineVertexIndex;
	CheckControlShowSplineVertexIndex.SetCheck(m_bShowSplineVertexIndex);
	m_pView->InvalidateRect(NULL,false);
	if(m_pDoc->pSideDoc==NULL)	return;
	if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
	m_pDoc->pSideDoc->m_pView->m_bShowSplineVertexIndex 
		= m_pView->m_bShowSplineVertexIndex;
	m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
}

void CDLG_2DSpline_Setting::OnBnClickedCheckShowSplineNormal()
{
	m_bShowNormal = !m_bShowNormal; 
	m_pView->m_bShowSplineNormal = m_bShowNormal;
	CheckControlShowNormal.SetCheck(m_bShowNormal);
	m_pView->InvalidateRect(NULL,false);
	if(m_pDoc->pSideDoc==NULL)	return;
	if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
	m_pDoc->pSideDoc->m_pView->m_bShowSplineNormal
		= m_pView->m_bShowSplineNormal;
		m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
}

void CDLG_2DSpline_Setting::OnBnClickedCheckShowColorline()
{
	m_bShowSplineColorLine = !m_bShowSplineColorLine; 
	m_pView->m_bColoredLines = m_bShowSplineColorLine;
	CheckControlShowSplineColorLine.SetCheck(m_bShowSplineColorLine);
	m_pView->InvalidateRect(NULL,false);
}

void CDLG_2DSpline_Setting::OnBnClickedCheckShowSplineInMeshView()
{
	if(m_pDoc->pSideDoc==NULL)
		return;
	if(m_pDoc->pSideDoc->m_pMesh==NULL)
		return;
	m_bShowInMeshView =! m_bShowInMeshView; 
	m_pDoc->pSideDoc->m_pView->m_bShowSplineInMeshView = m_bShowInMeshView;
	CheckControlShowInMeshView.SetCheck(m_bShowInMeshView);
	m_pDoc->pSideDoc->m_pView->Invalidate(false);	
}


void CDLG_2DSpline_Setting::OnBnClickedButton2dsplineSave()
{
	CString filename;	
	if(SavingDialog(filename, "sply","Save Polygons", G_RootFolder+"image_contours\\"))
	{
		m_pDoc->m_MultiPolygons->SaveToPLYFile(filename.GetBuffer(MAX_PATH));
		m_pView->InvalidateRect(NULL,false);
	}	
}

void CDLG_2DSpline_Setting::OnBnClickedButton2dsplineLoad()
{
	CString filename;
	if(LoadingDialog(filename, "sply","Load Polygons", G_RootFolder+"image_contours\\"))
	{
		m_pDoc->ClearSelectedPolys();
		m_pDoc->m_MultiPolygons->LoadPLYFile(filename.GetBuffer(MAX_PATH), false);
		m_pView->InvalidateRect(NULL,false);
		if(m_pDoc->pSideDoc==NULL)	return;
		if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
		m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
	}		
}

void CDLG_2DSpline_Setting::OnBnClickedButton2dsplineAddFromfile()
{
	CString filename;
	if(LoadingDialog(filename, "sply","Load Polygons", G_RootFolder+"image_contours\\"))
	{
		m_pDoc->ClearSelectedPolys();
		m_pDoc->m_MultiPolygons->LoadPLYFile(filename.GetBuffer(MAX_PATH), true);
		m_pView->InvalidateRect(NULL,false);
		if(m_pDoc->pSideDoc==NULL)	return;
		if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
		m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
	}
}

void CDLG_2DSpline_Setting::OnHScroll(UINT nSBCode, UINT nPos, CScrollBar* pScrollBar) 
{
	CWnd *pFocusWnd = GetFocus();
	switch(nSBCode)
	{
	case TB_BOTTOM:
	case TB_ENDTRACK:
	case TB_LINEDOWN:
	case TB_LINEUP:
	case TB_PAGEDOWN:
	case TB_PAGEUP:
	case TB_THUMBPOSITION:
	case TB_THUMBTRACK:
	case TB_TOP:
		if (&m_SliderSample == pFocusWnd) 
			UpdateSampleRate();
		break;
	default:
		break;
	}
	CDialog::OnHScroll(nSBCode, nPos, pScrollBar);
}


void CDLG_2DSpline_Setting::UpdateSampleRate(void)
{
	if( m_pDoc->m_ImageMouseCtrl== INPUTPOLY || m_pDoc->m_ImageMouseCtrl== INPUTSPLINE) 
		return;
	float Sr = (float)m_SliderSample.GetPos()/50.0;
	if(m_bOnlyIncrease && Sr<1) return;
	m_nVertexNum = m_pDoc->m_SelectedPolygons->ResampleByRatio(Sr); 
	if(m_pDoc->m_nSelectedPoly != 1) //only show one poly's info
	{
		CString str;	
		str.Format("Vertices: %d", m_nVertexNum);
		SetDlgItemText(IDC_STATIC_VN,str );
	}
	m_pView->InvalidateRect(NULL,false);
	if(m_pDoc->pSideDoc==NULL)	return;
	if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
	m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
}

afx_msg void CDLG_2DSpline_Setting::OnBnClickedCheck2dsplineKeepOriginVertex()
{
	m_bOnlyIncrease = !m_bOnlyIncrease;
	CheckControlKeepOriginV.SetCheck(m_bOnlyIncrease);
}

void CDLG_2DSpline_Setting::OnBnClickedButton2dsplineCloseUnclose()
{
	m_pDoc->m_SelectedPolygons->SwitchClosed(true);
	m_pView->InvalidateRect(NULL,false);
	if(m_pDoc->pSideDoc==NULL)	return;
	if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
	m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);	
}

// void CDLG_2DSpline_Setting::OnBnClickedButton2dsplineTriangulation()
// {
// 	int npoly = m_pDoc->m_MultiPolygons.NumPolygon();
// 	CString fname = m_pDoc->m_MultiPolygons.m_fname;
// 	CString idx;
// 	for (int i=0; i<npoly; ++i){
// 		CPolygon *poly = m_pDoc->m_MultiPolygons.GetPolygon(i);		
// 		idx.Format("_%d",i);
// 		CString str;
// 		EDTTriAvgArea.GetWindowText(str);
// 		double TriArea = atof(str);
// 		poly->DelaunayTriangulation(fname+idx, 0, m_pView->WindowSize.cy-1, TriArea,
// 			CHKAddFrameAsBorder.GetCheck(), m_pDoc->m_pImage->InitWidth,m_pDoc->m_pImage->InitHeight);
// 	}
// 	m_pView->InvalidateRect(NULL,false);
// 	if(m_pDoc->pSideDoc==NULL)	return;
// 	if(m_pDoc->pSideDoc->m_pMesh==NULL)	return;
// 	m_pDoc->pSideDoc->m_pView->InvalidateRect(NULL,false);		
// }


void CDLG_2DSpline_Setting::OnBnClickedButton2dsplineSetHolesForTrig()
{
	unsigned nSel= m_pDoc->m_MultiPolygons->NumPolygon();
	m_holeSet.clear();
	for (unsigned i=0; i<nSel; ++i){		
		CPolygon *ppl = m_pDoc->m_MultiPolygons->GetPolygon(i);
		if( m_pDoc->m_MultiPolygons->GetSelectdPolygons()->IsSelected(i)>-1 ){
			m_holeSet.push_back(i);
			std::cout<<"# : "<<m_holeSet.back()<<"\n"; 		
		}
	}
}
